home *** CD-ROM | disk | FTP | other *** search
/ Aminet 2 / Aminet AMIGA CDROM (1994)(Walnut Creek)[Feb 1994][W.O. 44790-1].iso / Aminet / game / role / ZorkMachine_1_15.LHA / code.c next >
C/C++ Source or Header  |  1992-04-22  |  8KB  |  352 lines

  1. /*
  2. *    @(#)code.c    2.24
  3. */
  4.  
  5. #include "zmachine.h"
  6.  
  7. #ifdef AMIGA
  8. #define TRACE 1
  9. #endif    /* AMIGA */
  10.  
  11. /*
  12. * decoding/encoding module
  13. */
  14.  
  15. char *codetab = 
  16. "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ  0123456789.,!?_#'\"/\\-:()\0";
  17.  
  18. extern UBYTE *short_cuts;
  19.  
  20. /*
  21. * decode the string at vaddress a
  22. */
  23.  
  24. #ifdef TRACE
  25. void ppdecode(a)
  26. struct address *a;
  27. {
  28.     UWORD op;
  29.     register UWORD d2;
  30.     register UWORD d4 = 0;
  31.     register UWORD d5 = 0;
  32.     register UBYTE *p;
  33.     struct address vaddr;
  34.     UWORD f76 = 0;
  35.     UBYTE b[3];
  36.  
  37.     do
  38.     {
  39.         op = d2 = fetchw_data(a);
  40.         for (p = b; p - b < 3; p++)
  41.         {
  42.             *p = d2;
  43.             d2 >>= 5;
  44.         }
  45.  
  46.         while (p - b > 0)
  47.         {
  48.             d2 = *--p & 0x1f;
  49.             if (d4 & 0x8000)
  50.             {
  51.                 waddr_to_vaddr(&vaddr, word_get(&short_cuts[(d2 + f76)*2]));
  52.         ppdecode(&vaddr);
  53.                 d4 = d5;
  54.             }
  55.             else
  56.             {
  57.                 if (d4 == 3)
  58.                     d4 = 0x4000 + d2;
  59.                 else if (d4 > 3)
  60.                 {
  61.                     d4 &= 3;
  62.                     d4 <<= 5;
  63.                     d4 |= d2;
  64. #ifdef AMIGA
  65.                     DPrintf("%lc",d4);
  66. #else
  67.                     output_chr(d4);
  68. #endif    /* AMIGA */
  69.                     d4 = d5;
  70.                 }
  71.                 else
  72.                 {
  73.                     if (d2 >= 6)
  74.                     {
  75.                         if (d4 == 2)
  76.                         {
  77.                             if (d2 < 7)
  78.                                 d4++;
  79.                             else if (d2 == 7)
  80.                             {
  81. #ifdef AMIGA
  82.                 DPrintf("\\n");
  83. #else
  84.                                 putchar('\n');
  85. #endif    /* AMIGA */
  86.                                 d4 = d5;
  87.                             }
  88.                             else
  89.                             {
  90. #ifdef AMIGA
  91.                 DPrintf("%lc",codetab[d4 * 0x1a + d2 - 6]);
  92. #else
  93.                                 putchar(codetab[d4 * 0x1a + d2 - 6]);
  94. #endif    /* AMIGA */
  95.                                 d4 = d5;
  96.                             }
  97.                         }
  98.                         else
  99.                         {
  100. #ifdef AMIGA
  101.                             DPrintf("%lc",codetab[d4 * 0x1a + d2 - 6]);
  102. #else
  103.                             putchar(codetab[d4 * 0x1a + d2 - 6]);
  104. #endif    /* AMIGA */
  105.                             d4 = d5;
  106.                         }
  107.                     }
  108.                     else
  109.                     {
  110.                         if (d2 == 0)
  111.                         {
  112. #ifdef AMIGA
  113.                             DPrintf(" ");
  114. #else
  115.                             putchar(' ');
  116. #endif    /* AMIGA */
  117.                             d4 = d5;
  118.                         }
  119.                         else
  120.                         {
  121.                             if (d2 <= 3)
  122.                             {
  123.                                 d4 |= ~0x7fff;
  124.                                 f76 = (d2 - 1) << 5;
  125.                             }
  126.                             else
  127.                             {
  128.                                 d2 -= 3;
  129.                                 if (d4 == 0)
  130.                                     d4 = d2;
  131.                                 else
  132.                                 {
  133.                                     if (d4 != d2)
  134.                                         d4 = 0;
  135.                     d5 = d4;
  136.                                 }
  137.                             }
  138.                         }
  139.                     }
  140.                 }
  141.             }
  142.         }
  143.     }
  144.     while (!(op & 0x8000));
  145. }
  146.  
  147. void pdecode(a)
  148. struct address *a;
  149.     {
  150.     struct address b;
  151.     b = *a;
  152.     ppdecode(a);
  153.     *a = b;
  154.     }
  155. #endif
  156.  
  157.  
  158. void decode(a)
  159. struct address *a;
  160. {
  161.     UWORD op;
  162.     register UWORD d2;
  163.     register UWORD d4 = 0;
  164.     register UWORD d5 = 0;
  165.     register UBYTE *p;
  166.     struct address vaddr;
  167.     UWORD f76 = 0;
  168.     UBYTE b[3];
  169.  
  170.     do
  171.     {
  172.         op = d2 = fetchw_data(a);
  173.         for (p = b; p - b < 3; p++)
  174.         {
  175.             *p = d2;
  176.             d2 >>= 5;
  177.         }
  178.  
  179.         while (p - b > 0)
  180.         {
  181.             d2 = *--p & 0x1f;
  182.             if (d4 & 0x8000)
  183.             {
  184.                 waddr_to_vaddr(&vaddr, word_get(&short_cuts[(d2 + f76)*2]));
  185.         decode(&vaddr);
  186.                 d4 = d5;
  187.             }
  188.             else
  189.             {
  190.                 if (d4 == 3)
  191.                     d4 = 0x4000 + d2;
  192.                 else if (d4 > 3)
  193.                 {
  194.                     d4 &= 3;
  195.                     d4 <<= 5;
  196.                     d4 |= d2;
  197.                     output_chr(d4);
  198.                     d4 = d5;
  199.                 }
  200.                 else
  201.                 {
  202.                     if (d2 >= 6)
  203.                     {
  204.                         if (d4 == 2)
  205.                         {
  206.                             if (d2 < 7)
  207.                                 d4++;
  208.                             else if (d2 == 7)
  209.                             {
  210.                                 output_chr('\n');
  211.                                 d4 = d5;
  212.                             }
  213.                             else
  214.                             {
  215.                                 output_chr(codetab[d4 * 0x1a + d2 - 6]);
  216.                                 d4 = d5;
  217.                             }
  218.                         }
  219.                         else
  220.                         {
  221.                             output_chr(codetab[d4 * 0x1a + d2 - 6]);
  222.                             d4 = d5;
  223.                         }
  224.                     }
  225.                     else
  226.                     {
  227.                         if (d2 == 0)
  228.                         {
  229.                             output_chr(' ');
  230.                             d4 = d5;
  231.                         }
  232.                         else
  233.                         {
  234.                             if (d2 <= 3)
  235.                             {
  236.                                 d4 |= ~0x7fff;
  237.                                 f76 = (d2 - 1) << 5;
  238.                             }
  239.                             else
  240.                             {
  241.                                 d2 -= 3;
  242.                                 if (d4 == 0)
  243.                                     d4 = d2;
  244.                                 else
  245.                                 {
  246.                                     if (d4 != d2)
  247.                                         d4 = 0;
  248.                     d5 = d4;
  249.                                 }
  250.                             }
  251.                         }
  252.                     }
  253.                 }
  254.             }
  255.         }
  256.     }
  257.     while (!(op & 0x8000));
  258. }
  259.  
  260.  
  261. /* return the code group of c */
  262.  
  263. UWORD code_group(c)
  264. register char c;
  265. {
  266.     if (!c)
  267.         return(3);
  268.  
  269.     if (c >= 'a' && c <= 'z')
  270.             return(0);
  271.  
  272.     if (c >= 'A' && c <= 'Z')
  273.             return(1);
  274.  
  275.     return(2);
  276. }
  277.  
  278. /*
  279. * return the index
  280. * of c in the codetab
  281. */
  282.  
  283. UWORD code_index(c)
  284. char c;
  285. {
  286.     register char *p;
  287.     register UWORD i;
  288.     char *strchr();
  289.  
  290.     p = strchr(codetab,c);
  291.  
  292.     if (p)
  293.     {
  294.         for (i = p - codetab + 6; i >= 0x20; i -= 0x1a)
  295.             ;
  296.         return(i);
  297.     }
  298.     else
  299.         return(0);
  300. }
  301.  
  302.  
  303. /*
  304. * code a word of
  305. * max 6 chars to dest
  306. */
  307.  
  308. void encode(dst, src)
  309. register UWORD *dst; char *src;
  310. {
  311.     register UWORD t, i;
  312.     register UWORD *tp;
  313.     UWORD b[12];
  314.     char c;
  315.  
  316.     for(tp = b, i = 6; (c = *(src++)) && i; i--)
  317.     {
  318.         if (t = code_group(c))
  319.         {
  320.             t += 3;
  321.             *(tp++) = t;
  322.             if (!--i)
  323.                 break;
  324.         }
  325.  
  326.         if (!(t = code_index(c)))
  327.         {
  328.             *(tp++) = 6;
  329.             if (!--i)
  330.                 break;
  331.             *(tp++) = c >> 5;
  332.             if (!--i)
  333.                 break;
  334.  
  335.             t = c & 0x1f;
  336.         }
  337.         *(tp++) = t;
  338.     }
  339.  
  340.     for (; i; i--)
  341.         *(tp++) = 5;
  342.  
  343.     for (tp = b, i = 2; i; i--)
  344.     {
  345.         t  = (*tp++ << 10) & (0x1f << 10);
  346.         t |= (*tp++ <<  5) & (0x1f <<  5);
  347.         t |= (*tp++)       & (0x1f);
  348.         *dst++ = t;
  349.     }
  350.     dst[-1] |= 0x8000;
  351. }
  352.